package com.logic.landseaserver.service.impl;

import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.stream.Collectors;

import javax.servlet.http.HttpServletResponse;


import com.logic.landseaserver.common.enums.ContractStatusCodeEnum;
import com.logic.landseaserver.common.LandseaErrorMessageEnum;

import com.logic.landseaserver.common.exception.LandseaBusinessException;
import com.logic.landseaserver.persistence.read.*;
import com.logic.landseaserver.persistence.write.ExpensesHistoryWriteMapper;
import com.logic.landseaserver.ws.request.AddMeterToExpenseReq;
import org.apache.commons.lang.time.DateUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.ss.usermodel.Font;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.ss.usermodel.WorkbookFactory;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.logic.common.domain.Code;
import com.logic.common.exception.BusinessException;
import com.logic.common.security.SecurityUtils;
import com.logic.common.util.PagingTool;
import com.logic.common.util.QueryCriteria;
import com.logic.common.util.QueryUtil;
import com.logic.common.util.SysUtil;
import com.logic.landseaserver.common.LandeaConstants.CheckType;
import com.logic.landseaserver.common.enums.BillStatusEnum;
import com.logic.landseaserver.common.enums.BillTypeEnum;
import com.logic.landseaserver.common.enums.ExpensesStatusEnum;
import com.logic.landseaserver.common.util.DateUtil;
import com.logic.landseaserver.common.util.LandSeaUtil;
import com.logic.landseaserver.domain.BillDetail;
import com.logic.landseaserver.domain.Expenses;
import com.logic.landseaserver.domain.MonthlyBill;
import com.logic.landseaserver.persistence.write.ExpensesWriteMapper;
import com.logic.landseaserver.persistence.write.MonthlyBillWriteMapper;
import com.logic.landseaserver.service.IExpensesService;
import com.logic.landseaserver.ws.dto.CheckFeeListDTO;
import com.logic.landseaserver.ws.dto.ContractMonthFeeDTO;
import com.logic.landseaserver.ws.dto.ExpensesDTO;
import com.logic.landseaserver.ws.dto.ProjectAppartmentDTO;
import com.logic.landseaserver.ws.dto.ReadMeterTimeDTO;
import com.logic.system.persistence.read.CodeReadMapper;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

@Service
public class ExpensesServiceImpl implements IExpensesService {

    private static final Logger LOG = LoggerFactory.getLogger(ExpensesServiceImpl.class);

    @Autowired
    private ExpensesReadMapper expensesReadMapper;

    @Autowired
    private ExpensesWriteMapper expensesWriteMapper;
    @Autowired
    private ExpensesHistoryWriteMapper expensesHistoryWriteMapper;

    @Autowired
    private ExpensesHistoryReadMapper expensesHistoryReadMapper;
    @Autowired
    private RoomReadMapper roomReadMapper;

    @Autowired
    private ContractReadMapper contractReadMapper;

    @Autowired
    private BillDetailReadMapper billDetailReadMapper;

    @Autowired
    private CheckFeeListReadMapper checkFeeListReadMapper;

    @Autowired
    private MonthlyBillWriteMapper monthlyBillWriteMapper;

    @Autowired
    private CodeReadMapper codeReadMapper;

    @Autowired
    private MeterDataReadMapper meterDataReadMapper;

    @Override
    public void delete(String arg0) throws BusinessException {
        String[] idArr = arg0.split(",");
        for (String id : idArr) {
            Integer expensesId = Integer.valueOf(id);
            Expenses expenses = (Expenses) this.get(expensesId);
            Boolean pass = this.validateForDelete(expenses);
            if (pass) {
                expenses.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
                expensesWriteMapper.deleteByPrimaryKey(expenses);
            }
        }

    }

    @Override
    public Object get(Integer arg0) throws BusinessException {
        return expensesReadMapper.selectByPrimaryKey(arg0);
    }

    @Override
    public int insert(Object arg0) throws BusinessException {
        Integer id = -1;
        Boolean pass = this.validateForInsert(arg0);
        if (pass) {
            Expenses expenses = (Expenses) arg0;
            expenses.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
            expensesWriteMapper.insertSelective(expenses);
            id = expenses.getId();
        }
        return id;
    }

    @Override
    public List<?> query(QueryUtil arg0) {
        return expensesReadMapper.getList(arg0);
    }

    @Override
    public void update(Object arg0) throws BusinessException {
        Boolean pass = this.validateForUpdate(arg0);
        if (pass) {
            Expenses expenses = (Expenses) arg0;
            expenses.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
            expenses.setCreatedBy(null);
            expenses.setCreatedDtm(null);
            expensesWriteMapper.updateByPrimaryKeySelective(expenses);
        }

    }

    @Override
    public Boolean validate(Object arg0) throws BusinessException {
        Boolean pass = true;
        return pass;
    }

    @Override
    public Boolean validateForDelete(Object arg0) throws BusinessException {
        return true;
    }

    @Override
    public Boolean validateForInsert(Object arg0) throws BusinessException {
        Boolean pass = false;
        pass = this.validate(arg0);
        return pass;
    }

    @Override
    public Boolean validateForUpdate(Object arg0) throws BusinessException {
        Boolean pass = false;
        pass = this.validate(arg0);
        return pass;
    }


    @Override
    public ExpensesDTO getDTO(Integer id) throws BusinessException {
        return expensesReadMapper.selectDTOByPrimaryKey(id);
    }

    @Override
    public List<ExpensesDTO> queryDTO(QueryUtil queryUtil) {
        return expensesReadMapper.getDTOList(queryUtil);
    }

    @Override
    public void downloadTemplate(HttpServletResponse response, Integer projectId, String expenseType) {

        InputStream ins = null;
        Workbook wb = null;
        try {
            ins = PropertyServiceImpl.class.getClassLoader().getResourceAsStream("抄表读数模板.xlsx");
            wb = WorkbookFactory.create(ins);
        } catch (FileNotFoundException e) {
            LOG.error("downloadTemplate error.", e);
        } catch (IOException e) {
            LOG.error("downloadTemplate error.", e);
        } catch (InvalidFormatException e) {
            LOG.error("downloadTemplate error.", e);
        } finally {
            try {
                ins.close();
            } catch (IOException e) {
                LOG.error("downloadTemplate close io error.", e);
            }
        }
        String fileName = "抄表读数模板.xlsx";
        QueryUtil queryUtil = new QueryUtil();
        PagingTool pagingTool = new PagingTool();
        pagingTool.setCurrentPage(1);
        pagingTool.setPageSize(-1);
        queryUtil.setPagingTool(pagingTool);
        QueryCriteria queryCriteria = new QueryCriteria();
        queryCriteria.setConnection("and");
        queryCriteria.setKey("prjId");
        queryCriteria.setCondition("=");
        queryCriteria.setValue(projectId + "");
        queryCriteria.setIsValueADigital(true);
        List<QueryCriteria> queryCriterias = new ArrayList<QueryCriteria>();
        queryCriterias.add(queryCriteria);
        queryUtil.setQueryCriterias(queryCriterias);
        List<Object> roomList = roomReadMapper.selectByPage(queryUtil);
        Integer downNo = expensesReadMapper.queryMaxNo(projectId);
        downNo = downNo == null ? 1 : downNo + 1;
        List<Expenses> expenseList = this.bulidExpense(roomList, expenseType, downNo);
        if (expenseList != null && expenseList.size() > 0) {
            expensesWriteMapper.insertBatch(expenseList);
            Expenses expenses = expenseList.get(0);
            String projectName = expenses.getPrjName();
            Code code = codeReadMapper.selectByPrimaryKey(expenseType);
            String expenseTypeDesc = code.getCodeDescZh();
            fileName = projectName + "_[" + expenseTypeDesc + "].xlsx";
        }
        QueryUtil queryUtil2 = new QueryUtil();
        PagingTool pagingTool2 = new PagingTool();
        pagingTool2.setCurrentPage(1);
        pagingTool2.setPageSize(-1);
        queryUtil2.setPagingTool(pagingTool2);

        QueryCriteria queryCriteria2 = new QueryCriteria();
        queryCriteria2.setConnection("and");
        queryCriteria2.setKey("prj_id");
        queryCriteria2.setCondition("=");
        queryCriteria2.setValue(projectId + "");
        queryCriteria2.setIsValueADigital(true);

        QueryCriteria queryCriteria3 = new QueryCriteria();
        queryCriteria3.setConnection("and");
        queryCriteria3.setKey("type");
        queryCriteria3.setCondition("=");
        queryCriteria3.setValue(expenseType);
        queryCriteria3.setIsValueADigital(false);

        QueryCriteria queryCriteria4 = new QueryCriteria();
        queryCriteria4.setConnection("and");
        queryCriteria4.setKey("status");
        queryCriteria4.setCondition("=");
        queryCriteria4.setValue(ExpensesStatusEnum.ES1.getCode());
        queryCriteria4.setIsValueADigital(false);

        QueryCriteria queryCriteria5 = new QueryCriteria();
        queryCriteria5.setConnection("and");
        queryCriteria5.setKey("opr_batch");
        queryCriteria5.setCondition("=");
        queryCriteria5.setValue(downNo.toString());
        queryCriteria5.setIsValueADigital(false);

        List<QueryCriteria> queryCriterias2 = new ArrayList<QueryCriteria>();
        queryCriterias2.add(queryCriteria2);
        queryCriterias2.add(queryCriteria3);
        queryCriterias2.add(queryCriteria4);
        queryCriterias2.add(queryCriteria5);
        queryUtil2.setQueryCriterias(queryCriterias2);
        List<?> list = this.queryDTO(queryUtil2);
        if (list != null && list.size() > 0) {
            Sheet sheet = wb.getSheet("抄表读数列表");
            // 生成一个样式
            CellStyle style = wb.createCellStyle();
            // 设置这些样式
            style.setAlignment(CellStyle.ALIGN_CENTER);
            // 生成一个字体
            Font font = wb.createFont();
            font.setFontHeightInPoints((short) 14);
            font.setBoldweight(Font.BOLDWEIGHT_BOLD);
            Row row;
            Cell cell;// 产生单元格
            // 把字体应用到当前的样式
            style.setFont(font);
            int startRow = 1;
            for (int i = 0; i < list.size(); i++) {
                ExpensesDTO object = (ExpensesDTO) list.get(i);
                row = sheet.createRow(startRow);
                row.createCell(0).setCellType(Cell.CELL_TYPE_STRING);
                row.createCell(0).setCellValue(object.getId());
                row.createCell(1).setCellValue(object.getRoomId());
                row.createCell(2).setCellValue(object.getPrjName());
                row.createCell(3).setCellValue(object.getBuildNum());
                row.createCell(4).setCellValue(object.getUnitNum());
                row.createCell(5).setCellValue(object.getFloorNum());
                row.createCell(6).setCellValue(object.getHouseNum());
                row.createCell(7).setCellValue(object.getTypeDesc());
                startRow++;
            }
            response.setContentType("application/vnd.ms-excel;charset=utf-8");
            response.setContentType("APPLICATION/OCTET-STREAM");
            try {
                response.setHeader("Content-Disposition",
                        "attachment; filename=" + new String(fileName.getBytes("gb2312"), "ISO8859-1"));
            } catch (UnsupportedEncodingException e) {
                LOG.error("downloadTemplate close io error.", e);
            }
            OutputStream out = null;
            try {
                out = response.getOutputStream();
                wb.write(out);
            } catch (IOException e) {
                LOG.error("downloadTemplate close io error.", e);
            }


        }
    }

    private List<Expenses> bulidExpense(List<Object> list, String expenseType, Integer batchNo) {
        List<Expenses> expensList = new ArrayList<>();
        for (Object object : list) {
            ProjectAppartmentDTO projectAppartmentDTO = (ProjectAppartmentDTO) object;
            Expenses expense = this.bulidExpense(projectAppartmentDTO, expenseType, batchNo);
            expensList.add(expense);
        }
        return expensList;
    }

    private Expenses bulidExpense(ProjectAppartmentDTO projectAppartmentDTO, String expenseType, Integer batchNo) {
        Expenses expense = new Expenses();
        expense.setPrjId(projectAppartmentDTO.getPrjId());
        expense.setPrjName(projectAppartmentDTO.getPrjName());
        expense.setRoomId(projectAppartmentDTO.getId());
        expense.setBuildNum(projectAppartmentDTO.getBuildNum());
        expense.setUnitNum(projectAppartmentDTO.getUnitNum());
        expense.setFloorNum(projectAppartmentDTO.getFloorNum());
        expense.setHouseNum(projectAppartmentDTO.getHouseNum());
        expense.setType(expenseType);
        expense.setOprBatch(batchNo);
        //添加信息来源：手抄
        expense.setSource(0);
        expense.setStatus(ExpensesStatusEnum.ES1.getCode());//new
        return expense;
    }

    @Override
    public void batchInsert(List<Expenses> list) {
        for (Expenses expense : list) {
            try {
                this.insert(expense);
            } catch (BusinessException e) {
                LOG.error("batchInsert error.", e);
            }
        }
    }

    @Override
    public ReadMeterTimeDTO importFee(InputStream file) throws BusinessException {
        StringBuffer sb = new StringBuffer();
        Workbook workbook = null;
        String projectName = null;
        Integer expenseId = null;
        Integer roomId = null;
        try {
            workbook = WorkbookFactory.create(file);
        } catch (IOException e) {
            LOG.error("importFee error.", e);
        } catch (InvalidFormatException e) {
            LOG.error("importFee error.", e);
        }
        try {
            Sheet sheet = workbook.getSheetAt(0);
            Row row = null;
            int count = sheet.getPhysicalNumberOfRows();
            if (count <= 1) {
                sb.append("表格缺少数据");
            }
            projectName = sheet.getRow(1).getCell(2).toString().trim();
            List<Expenses> expensesList = new ArrayList<>();
            for (int i = 1; i < count; i++) {
                row = sheet.getRow(i);
                if (row != null) {
                    Cell cell0 = row.getCell(0);
                    String idString = null;
                    if (cell0 != null) {
                        idString = cell0.toString().trim().split("\\.")[0];
                    }
                    Cell cell1 = row.getCell(1);
                    String roomIdString = null;
                    if (cell1 != null) {
                        roomIdString = cell1.toString().trim().split("\\.")[0];
                    }
                    Cell cell8 = row.getCell(8);
                    String readMeterTimeString = null;
                    if (cell8 != null) {
                        readMeterTimeString = cell8.toString().trim();
                    }
                    Cell cell9 = row.getCell(9);
                    String degreeString = null;
                    if (cell9 != null) {
                        degreeString = cell9.toString().trim();
                    }
                    Expenses expense = new Expenses();
                    if (StringUtils.isNotBlank(idString)) {
                        expenseId = Integer.valueOf(idString);
                        expense.setId(expenseId);
                    }
                    if (StringUtils.isNotBlank(roomIdString)) {
                        roomId = Integer.valueOf(roomIdString);
                        expense.setRoomId(roomId);
                    }
                    if (StringUtils.isNotBlank(readMeterTimeString)) {
                        expense.setReadMeterTime(SysUtil.convertStringToDate(readMeterTimeString, "yyyyMMdd"));
                    }
                    if (StringUtils.isNotBlank(degreeString)) {
                        expense.setDegree(Double.valueOf(degreeString));
                    }
                    if (StringUtils.isNotBlank(idString)
                            && StringUtils.isNotBlank(readMeterTimeString)
                            && StringUtils.isNotBlank(degreeString)) {
                        expense.setStatus(ExpensesStatusEnum.ES2.getCode());//import
                        expense.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
                        expensesList.add(expense);
                    }
                }
            }
            if (!sb.toString().equals("")) {
                throw new BusinessException(sb.toString());
            }
            Expenses fromDB = (Expenses) this.get(expenseId);
            if (expensesList != null && expensesList.size() > 0) {
                for (Expenses expenses : expensesList) {
                    if (expenses != null) {
                        Expenses expenses2 = expensesReadMapper.checkExistExpenses(expenses.getRoomId(), fromDB.getType(), expenses.getReadMeterTime());
                        if (expenses2 != null) {
                            expenses.setId(expenses2.getId());
                        }
                    }
                }
                expensesWriteMapper.updateByPrimaryKeySelectiveBatch(expensesList);
            }
        } catch (Exception exx) {
            LOG.error("数据导入异常", exx);
            throw new BusinessException(sb.toString());
        }
        ReadMeterTimeDTO readMeterTimeDTO = new ReadMeterTimeDTO();
        Expenses expenses = (Expenses) this.get(expenseId);
        Integer projectId = expensesReadMapper.getProjectIdByProjectName(projectName);
        String type = expenses.getType();
        Date maxReadMeterTime = expensesReadMapper.getMaxReadMeterTimeByProjectId(projectId, type);
        Date minReadMeterTime = expensesReadMapper.getMinReadMeterTimeByProjectId(projectId, type);
        readMeterTimeDTO.setProjectId(projectId);
        readMeterTimeDTO.setMaxReadMeterTime(SysUtil.convertDateToString(maxReadMeterTime, "yyyy-MM-dd"));
        readMeterTimeDTO.setMinReadMeterTime(SysUtil.convertDateToString(minReadMeterTime, "yyyy-MM-dd"));
        readMeterTimeDTO.setType(expenses == null ? null : expenses.getType());
        return readMeterTimeDTO;
    }

    @Override
    @Transactional(propagation = Propagation.SUPPORTS, rollbackFor = {BusinessException.class,
            LandseaBusinessException.class, Exception.class})
    public void backupexpenses() {

        List<Expenses> list = expensesReadMapper.backupExpenses();

        if (list != null && list.size() > 0) {
            //备份到新表
            expensesHistoryWriteMapper.batchBackUp(list);
            //获取新记录标记
            Integer maxId = expensesHistoryReadMapper.getMaxId();
            //删除旧表记录
            expensesWriteMapper.delete(maxId);
        }

    }

    @Override
    public void batchInertMonthly() throws BusinessException {
        //查询符合条件的合同列表
        String billMonth = DateUtil.getInstence().convertYM(new Date());
        List<ContractMonthFeeDTO> contractList = contractReadMapper.queryContractFee(null, ContractStatusCodeEnum.SIGN.getCode());
        List<Integer> ids = new ArrayList<>();
        for (ContractMonthFeeDTO cdto : contractList) {
            ids.add(cdto.getRoomId());
        }
        List<Expenses> exList = new ArrayList<>();
        //查询需要处理的记录
        if (ids.size() > 0) {
            exList = expensesReadMapper.queryListByRoomIds(ids);
        }
        if (exList.size() > 0) {
            /*for(Expenses exp:exList){
                exp.setType(StringTools.getEmunCode(exp.getType()));
			}*/
        } else {
            return;
        }
        //需要处理的费用类型
        String[] feeTypes = {BillTypeEnum.CTBI1.getCode(), BillTypeEnum.CTBI2.getCode(), BillTypeEnum.CTBI3.getCode(),
                BillTypeEnum.CTBI4.getCode()};
        //根据合同处理需要导入的数据
        for (ContractMonthFeeDTO cdto : contractList) {
            try{
                //如果是换转续合同则不处理水电了
                if(!StringUtils.isEmpty(cdto.getRentStatus())){
                    continue;
                }
                //取出上一次缴费记录
                HashMap map = new HashMap();
                map.put("types", feeTypes);
                map.put("contractId", cdto.getId());
                List<BillDetail> billDetails = billDetailReadMapper.queryLastBillType(map);
                //该合同入住单
                List<CheckFeeListDTO> checkList = null;
                //查询出房间对应的记录
                for (String feeType : feeTypes) {
                /*if(cdto.getId()==113 || cdto.getId()==114 || cdto.getId()==115){
				//	exList.forEach(e -> log.info("sss"+e.getRoomId().equals(cdto.getRoomId())));
				}*/
                    //抄表日期要大于入住日
                    List<Expenses> roomExList = exList.stream().filter(e -> e.getRoomId().equals(cdto.getRoomId()) && e.getType().equals(feeType)
                            && DateUtil.compareTime(e.getReadMeterTime(), cdto.getInDate()) > 0)
                            .collect(Collectors.toList());
                    if (roomExList.size() > 0) {
                        //上次抄表用量
                        Double lastCutNum = 0.0;
                        //上次抄表日期
                        Date lastReadTime = cdto.getInDate();
                        //此次抄表用量
                        Double nowCutNum = roomExList.get(0).getDegree();
                        //此次抄表日期
                        Date nowReadTime = roomExList.get(0).getReadMeterTime();
                        Optional<BillDetail> billDt = billDetails.stream().filter(e -> e.getType().equals(feeType)).findFirst();
                        //如果存在上一次账单结清日
                        if (billDt.isPresent()) {
                            //查询上次入库记录
                            HashMap qMap = new HashMap();
                            qMap.put("roomId", cdto.getRoomId());
                            qMap.put("status", ExpensesStatusEnum.ES3.getCode());
                            qMap.put("type", feeType);
                            qMap.put("inDate", DateUtil.getInstence().convertDate(billDt.get().getDateEnd()));
                            Expenses lastEx = expensesReadMapper.querExpenses(qMap);
                            if (lastEx != null) {
                                lastCutNum = lastEx.getDegree();
                                lastReadTime = lastEx.getReadMeterTime();
                                if (DateUtil.compareTime(lastReadTime, nowReadTime) > 0) {
                                    LOG.info("has not query last exp indata：" + cdto.getId() + " fee type is :" + feeType);
                                    continue;
                                }
                                lastReadTime = DateUtils.addDays(lastReadTime, 1);
                            } else {
                                LOG.info("has not query last exp indata：" + cdto.getId() + " fee type is :" + feeType);
                                continue;
                            }
                        } else {
                            //查询入住单 只有为空才去查询
                            if (checkList == null) {
                                Map<String, Object> queryParamMap = new HashMap<String, Object>();
                                queryParamMap.put("contractId", cdto.getId());
                                queryParamMap.put("checkType", CheckType.IN_COMING);
                                checkList = checkFeeListReadMapper.selectByContractIdAndCheckType(queryParamMap);
                            }
                            if (checkList != null) {
                                //取出入住单该费项的录入记录
                                Optional<CheckFeeListDTO> feeChecked = checkList.stream().filter(e -> e.getType().equals(feeType)).findFirst();
                                if (!feeChecked.isPresent()) {
                                    LOG.info("该合同未入住单为空1：" + cdto.getId());
                                    continue;
                                }
                                lastCutNum = feeChecked.get().getConsumptionEnd();
                                lastReadTime = feeChecked.get().getInDate();
                            } else {
                                LOG.info("该合同未入住单为空：" + cdto.getId());
                                continue;
                            }
                        }
                        //计算用量 新增monthly记录
                        if(nowCutNum==null || lastCutNum==null){
                            LOG.info("has no Currect used");
                        }
                        Double usedNum = LandSeaUtil.get2Double(nowCutNum - lastCutNum);
                        if (usedNum < 0) {
                            //不处理
                            LOG.info("has no Currect used：" + nowCutNum + " lastCutNum type is :" + lastCutNum + " contract id is:" + cdto.getId());
                            continue;
                        }
                        createOrUpdateEx(billMonth, cdto, feeType, roomExList, lastReadTime, nowReadTime, usedNum);
                    }
                }
            }
            catch (Exception e){
                LOG.info("Contract id is :"+cdto.getId()+"batchInertMonthly INSERT EROOR:"+e.getMessage());
            }

        }
    }

    private void createOrUpdateEx(String billMonth, ContractMonthFeeDTO cdto, String feeType, List<Expenses> roomExList, Date lastReadTime, Date nowReadTime, Double usedNum) {
        MonthlyBill monthlyBill = new MonthlyBill();
        monthlyBill.setBillMonth(billMonth);
        monthlyBill.setConsumption(usedNum);
        monthlyBill.setBillPrice(calculationPrice(feeType, cdto, usedNum));
        monthlyBill.setContractId(cdto.getId());
        monthlyBill.setRoomId(cdto.getRoomId());
        monthlyBill.setStatus(BillStatusEnum.BIST3.getCode());
        monthlyBill.setExpenseType(feeType);
        monthlyBill.setStartTime(lastReadTime);
        monthlyBill.setEndTime(nowReadTime);
        monthlyBill.setInputType(2);
        monthlyBill.updateCommonInfo(-1);
        monthlyBillWriteMapper.insertSelective(monthlyBill);
        //修改expense记录
        Expenses updateEx = new Expenses();
        updateEx.setId(roomExList.get(0).getId());
        updateEx.setStatus(ExpensesStatusEnum.ES3.getCode());
        updateEx.updateCommonInfo(-1);
        expensesWriteMapper.updateByPrimaryKeySelective(updateEx);

        int exSize = roomExList.size();
        if (exSize > 1) {
            List<Integer> exIds = new ArrayList<>();
            for (int i = 1; i < roomExList.size(); i++) {
                exIds.add(roomExList.get(i).getId());
            }
            HashMap updateExsMap = new HashMap();
            updateExsMap.put("status", ExpensesStatusEnum.ES4.getCode());
            updateExsMap.put("ids", exIds);
            expensesWriteMapper.updateStatus(updateExsMap);
        }
    }

    private Double calculationPrice(String feeType, ContractMonthFeeDTO cmDto, Double consumption) {
        Double billPrice = 0.0;
        //计算水
        if (feeType.equals(BillTypeEnum.CTBI1.getCode())) {
            return LandSeaUtil.get2Double(consumption * cmDto.getWaterPrice());
        } else if (feeType.equals(BillTypeEnum.CTBI2.getCode())) {
            return LandSeaUtil.get2Double(consumption * cmDto.getElectricPrice());
        } else if (feeType.equals(BillTypeEnum.CTBI3.getCode())) {
            return LandSeaUtil.get2Double(consumption * cmDto.getGasPrice());
        } else if (feeType.equals(BillTypeEnum.CTBI4.getCode())) {
            return LandSeaUtil.get2Double(consumption * cmDto.getHotWaterPrice());
        } else {
            return billPrice;
        }
    }

    @Override
    public void batchInsertDingxinDate(String date) throws LandseaBusinessException {

        if (org.apache.commons.lang.StringUtils.isEmpty(date)) {
            throw new LandseaBusinessException(LandseaErrorMessageEnum.BATCH_INSERT_EXPENSES_DXIN);
        }
        List<Expenses> list = meterDataReadMapper.selectExpensesData(date);

        if (list.size() > 0) {
            expensesWriteMapper.insertBatch(list);
        }
    }

    @Override
    public void batchInsertDingxinDatePrj(Object object) throws LandseaBusinessException {
        AddMeterToExpenseReq meterToExpenseReq = (AddMeterToExpenseReq) object;
        if (org.apache.commons.lang.StringUtils.isEmpty(meterToExpenseReq.getUserDate())) {
            throw new LandseaBusinessException(LandseaErrorMessageEnum.BATCH_INSERT_EXPENSES_DXIN);
        }
        if (org.apache.commons.lang.StringUtils.isEmpty(meterToExpenseReq.getProjectIds())) {
            throw new LandseaBusinessException(LandseaErrorMessageEnum.BATCH_PROJECT_INSERT_EXPENSES_DXIN);
        }
        List<Integer> ids = new ArrayList<>();
        String[] sIds = meterToExpenseReq.getProjectIds().split(",");
        for(String pId: sIds){
            ids.add(Integer.parseInt(pId));
        }
        HashMap<String ,Object> map = new HashMap<>();
        map.put("usedDate",meterToExpenseReq.getUserDate());
        map.put("ids",ids);
        List<Expenses> list = meterDataReadMapper.selectExpensesDataByPrj(map);
        System.out.println("处理运营数据共"+list.size());
        if (list.size() > 0) {
            expensesWriteMapper.insertBatch(list);
        }
    }


}
